package com.aqie.security.demo.controller;

import com.aqie.security.demo.web.async.DeferredResultHolder;
import com.aqie.security.demo.web.async.MockQueue;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.RandomStringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.context.request.async.DeferredResult;

import java.util.concurrent.Callable;

/**
 * @Function:
 * @Author: aqie
 * @Date: 2019/4/4 16:36
 */
@RestController
@Slf4j
public class AsyncController {

    @Autowired
    private MockQueue mockQueue;

    @Autowired
    private DeferredResultHolder deferredResultHolder;

    /**
     * 耗时 1004ms ： p-nio-80-exec-7
     */
    @RequestMapping("/order")
    public String order() throws Exception {
        log.info("主线程开始");
        Thread.sleep(1000);
        log.info("主线程返回");
        return "success";
    }

    /**
     * 两个日志在同一线程 耗时50ms，但是接口响应依旧是1000ms
     * 只是提高服务器 处理能力
     * 单开子线程 ： task-1
     */
    @RequestMapping("/ordercall")
    public Callable<String> orderCall() throws Exception {
        return () -> {
            log.info("主线程开始");
            Thread.sleep(1000);
            log.info("主线程返回");
            return "success";
        };
    }

    /**
     * 用对象模拟消息队列
     * @return
     * @throws Exception
     */
    @RequestMapping("/orderdefer")
    public DeferredResult<String> orderDefer() throws Exception {
        log.info("主线程开始");
        String orderNumber = RandomStringUtils.randomNumeric(8);
        mockQueue.setPlaceOrder(orderNumber);

        DeferredResult<String> result = new DeferredResult<>();
        deferredResultHolder.getMap().put(orderNumber, result);
        return result;
    }
}
